package com.quanxiaoha.weblog.common.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.quanxiaoha.weblog.common.domain.entity.ScheduleSkill;
import com.quanxiaoha.weblog.common.domain.entity.ScheduleSkillStage;
import com.quanxiaoha.weblog.common.domain.mapper.ScheduleSkillMapper;
import com.quanxiaoha.weblog.common.domain.query.ScheduleSkillQuery;
import com.quanxiaoha.weblog.common.domain.query.SkillQuery;
import com.quanxiaoha.weblog.common.domain.vo.CountVo;
import com.quanxiaoha.weblog.common.domain.vo.ScheduleSkillVo;
import com.quanxiaoha.weblog.common.service.IScheduleSkillService;
import com.quanxiaoha.weblog.common.service.IScheduleSkillStageService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * <p>
 *  服务实现类
 * </p>
 *
 * @author Roy
 * @since 2025-05-28
 */
@Service
@Slf4j
public class ScheduleSkillServiceImpl extends ServiceImpl<ScheduleSkillMapper, ScheduleSkill> implements IScheduleSkillService {


    @Autowired
    private IScheduleSkillStageService scheduleSkillStageService;

    @Resource
    ThreadPoolTaskExecutor taskExecutor;

    @Override
    public List<ScheduleSkillVo> getSkillList(SkillQuery skillQuery) {
        LambdaQueryWrapper<ScheduleSkill> queryWrapper = new LambdaQueryWrapper<>();
        // 根据名称模糊查询
        if (skillQuery.getSkillName() != null) {
            queryWrapper.like(ScheduleSkill::getSkillName, skillQuery.getSkillName());
        }
        // 根据完成状态查询
        if (skillQuery.getIsCompleted() != null) {
            queryWrapper.eq(ScheduleSkill::getIsCompleted, skillQuery.getIsCompleted());
        }
        queryWrapper.orderByDesc(ScheduleSkill::getCreateTime);
        Page<ScheduleSkill> page = this.page(new Page<>(skillQuery.getPageNum(), skillQuery.getPageSize()), queryWrapper);
        List<ScheduleSkillVo> scheduleSkillVos = BeanUtil.copyToList(page.getRecords(), ScheduleSkillVo.class);
        scheduleSkillVos.forEach(scheduleSkillVo -> {
            scheduleSkillVo.setStageVos(scheduleSkillStageService.getStageList(scheduleSkillVo.getId()));
        });
        return scheduleSkillVos;
    }

    @Override
    public ScheduleSkill getSkillDetail(Integer id) {
        return this.getById(id);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void createSkill(ScheduleSkillQuery skill) {

        log.info("新增技能：{}", skill);
        ScheduleSkill scheduleSkill = BeanUtil.copyProperties(skill, ScheduleSkill.class);
        // 新增技能练习默认为未完成
        scheduleSkill.setIsCompleted(1);
        scheduleSkill.setCreateTime(LocalDateTime.now());
        scheduleSkill.setUpdateTime(LocalDateTime.now());
        this.save(scheduleSkill);

        scheduleSkillStageService.saveStage(scheduleSkill.getId(),skill.getStageVos());
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateSkill(ScheduleSkill skill) {
        if (skill.getIsCompleted() == 2) {
            skill.setCompletedTime(LocalDateTime.now());
        }
        skill.setUpdateTime(LocalDateTime.now());
        this.updateById(skill);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void produce(ScheduleSkill skill) {

        ScheduleSkill byId = this.getById(skill.getId());
        if (Objects.nonNull(byId)) {
            byId.setUpdateTime(LocalDateTime.now());
            byId.setProduce(skill.getProduce());
            this.updateById(byId);
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteSkill(Integer id) {
        this.removeById(id);
        scheduleSkillStageService.remove(new LambdaQueryWrapper<ScheduleSkillStage>().eq(ScheduleSkillStage::getSkillId, id));
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateCompletedStatus(Integer id, Integer isCompleted) {
        ScheduleSkill skill = this.getById(id);
        if (skill != null) {
            skill.setIsCompleted(isCompleted);
            skill.setUpdateTime(LocalDateTime.now());
            this.updateById(skill);
        }
    }

    @Override
    @Async("taskExecutor")
    @Transactional(rollbackFor = Exception.class)
    public void checkStage(Integer stageId) {

        //打卡，完成阶段打勾
        ScheduleSkillStage byId = scheduleSkillStageService.getById(stageId);
        if (Objects.isNull(byId)) return;
        byId.setCompleted(2);
        scheduleSkillStageService.updateById(byId);

        //全部完成，就完成任务
        List<ScheduleSkillStage> list = scheduleSkillStageService.list(new LambdaQueryWrapper<ScheduleSkillStage>()
                .eq(ScheduleSkillStage::getSkillId, byId.getSkillId())
                .eq(ScheduleSkillStage::getCompleted, 1));
        if (list.isEmpty()) {
            ScheduleSkill skill = this.getById(byId.getSkillId());
            if (Objects.isNull(skill)) return;
            skill.setIsCompleted(2);
            skill.setCompletedTime(LocalDateTime.now());
            this.updateById(skill);
        }
    }

    @Override
    public List<CountVo> getCountVos() {

        List<ScheduleSkill> list = this.list(new LambdaQueryWrapper<ScheduleSkill>()
                .eq(ScheduleSkill::getIsCompleted, 1)
                .orderByDesc(ScheduleSkill::getCreateTime));
        if(list.isEmpty()) return Collections.emptyList();
        List<CountVo> countVos = new ArrayList<>();
        list.forEach(skill -> {
            ScheduleSkillStage one = scheduleSkillStageService.getOne(new LambdaQueryWrapper<ScheduleSkillStage>()
                    .eq(ScheduleSkillStage::getSkillId, skill.getId())
                    .eq(ScheduleSkillStage::getCompleted, 1)
                    .last("limit 1"));
            CountVo countVo = new CountVo();
            countVo.setRecordName(skill.getSkillName());
            countVo.setId(one.getId());
            countVo.setDescription("任务："+skill.getSkillName()+"\n"+"阶段："+one.getStageName()+"\n"+"节点："+one.getNodeName());
            countVo.setIsTask(true);
            countVos.add(countVo);
        });
        return countVos;
    }
}
